/*
 * To change this license header, choose License Headers in Project Properties.
 * To change this template file, choose Tools | Templates
 * and open the template in the editor.
 */
package cn.ac.iie.di.ban.ycl.bk.e2p.ysyb.thread;

import cn.ac.iie.di.ban.ycl.bk.e2p.ysyb.main.BanBkE2p;
import static cn.ac.iie.di.ban.ycl.bk.e2p.ysyb.main.BanBkE2p.alltimeout;
import cn.ac.iie.di.ban.ycl.bk.e2p.ysyb.service.FJRThreadTask;
import cn.ac.iie.di.ban.ycl.bk.e2p.ysyb.tools.PatternTools;
import java.io.File;
import java.io.Serializable;
import java.util.ArrayList;
import java.util.Iterator;
import java.util.List;
import java.util.concurrent.ArrayBlockingQueue;
import java.util.concurrent.ThreadPoolExecutor;
import java.util.concurrent.TimeUnit;
import org.apache.log4j.Logger;

/**
 *
 * @author wmr
 */
public class BKThread implements Runnable, Serializable{
    
    private static Logger logger = Logger.getLogger(BKThread.class);
    private String localPath;
    public BKThread(String localPath) {
        this.localPath = localPath;
    }
    
    public void run() {
        traverseFolderBK(localPath);
    }
    
    private static void execute(String localFilePath) {
        logger.info("获取任务目录：" + localFilePath + "/Ctrl");
        String nameSpace = localFilePath.substring(localFilePath.lastIndexOf("/") + 1, localFilePath.length());
        String[] temNameSpace = nameSpace.split("_");
        String sourceFileType;
        if (temNameSpace.length == 2) {
            sourceFileType = nameSpace.split("_")[1];
        } else {
            logger.error("nameSpace Directory structure error!!!");
            return;
        }
        String ctrlPath = localFilePath + "/Ctrl";
        File fileRoot = new File(ctrlPath);
        //return 回到死循环。return之前设置为null，提示JVM可以进行垃圾回收了
        if (!fileRoot.isDirectory()) {//ctrlPath 错误的情况
            logger.fatal("**********************************************************");
            logger.fatal("获取任务目录：" + ctrlPath + " 不存在。");
            logger.fatal("**********************************************************");
            fileRoot = null;
            return;
        }
        String[] allFileList = fileRoot.list();//所有json文件名
        //没有sql文件返回
        if (allFileList.length < 1) {
            logger.info("获取任务目录下没有文件");
            return;
        }
        //判断是否为文件夹
        if (allFileList.length == 1) {
            File fileFlag = new File(ctrlPath + File.separator + allFileList[0]);
            if (fileFlag.isDirectory()) {//是文件夹跳过
                return;
            }
        }

        List<String> jsonNameList = new ArrayList<String>();
        List<String> okList = new ArrayList<String>();
        List<String> dwdList = new ArrayList<String>();
        List<String> otherdwdList = new ArrayList<String>();
        List<String> otherList = new ArrayList<String>();
        for (String f : allFileList) {
            if (PatternTools.matchStr("json", f)) {
                if (f.contains("." + sourceFileType + ".dwd")) {
                    dwdList.add(f);
                } else if (f.endsWith(".ok")) {
                    okList.add(f);
                } else if (f.endsWith(".dwd")) {
                    otherdwdList.add(f);
                } else if (f.endsWith(".json")) {
                    jsonNameList.add(f);
                } else {
                    otherList.add(f);
                }
            }
        }

        //起线程池
        long begin = System.currentTimeMillis();
        ThreadPoolExecutor threadPool = new ThreadPoolExecutor(10, 100, 3,
                TimeUnit.SECONDS, new ArrayBlockingQueue<Runnable>(jsonNameList.size()),
                new ThreadPoolExecutor.DiscardOldestPolicy());
//        if(jsonNameList.isEmpty()){
//            logger.info( ctrlPath + "任务目录下没有要执行的文件 !!!");
//            return;
//        }
        for (int i = 0; i < jsonNameList.size(); i++) {
            if (PatternTools.matchStr("json", jsonNameList.get(i))) {
                String tmpname = jsonNameList.get(i) + ".ok";
                for (int j = 0; j < okList.size(); j++) {
                    if (tmpname.equals(okList.get(j))) {
                        boolean flag = false;
                        for (int k = 0; k < dwdList.size(); k++) {
                            String tmpdwdname = jsonNameList.get(i) + "." + sourceFileType + ".dwd";
                            if (tmpdwdname.equals(dwdList.get(k))) {
                                flag = true;
                                break;
                            }
                        }
                        if (!flag) {
                            //判断是否已经开始运行
                            boolean alreadyExecute = false;
                            Iterator<String> itr = BanBkE2p.threadList.iterator();
                            while (itr.hasNext()) {
                                if (!itr.next().equals(jsonNameList.get(i))) {
                                } else {
                                    alreadyExecute = true;
                                    break;
                                }
                            }
                            if (alreadyExecute) {
                                logger.info(jsonNameList.get(i) + "正在运行，跳过。");
                                continue;
                            } else {
                                //没有运行添加到队列中
                                BanBkE2p.threadList.add(jsonNameList.get(i));
                            }
                            threadPool.execute(new FJRThreadTask(jsonNameList.get(i), BanBkE2p.timeout, localFilePath));
                        }

                    }
                }
            }
        }

        while (true) {//直至所有线程结束，才继续
            int activeThread = threadPool.getActiveCount();
            if (activeThread == 0) {
                break;
            } else {
                try {
                    long end = System.currentTimeMillis();
                    long middle = (end - begin) / 1000;
                    long tmpTimeout = Long.parseLong(alltimeout);
                    if (middle < tmpTimeout) {
                        logger.info(" runtime:" + middle + " timeout:" + alltimeout);
                        Thread.sleep(3000);
                    } else {
                        logger.error(" upload is killed, because of timeout!");
                        threadPool.shutdown();
                        fileRoot = null;
                        allFileList = null;
                        echoRunning();
                        return;
                    }
                    Thread.sleep(1000);
                } catch (InterruptedException ex) {
                    logger.error(" sleep error " + ex.getMessage(), ex);
                }
            }
        }
        threadPool.shutdown();

        fileRoot = null;
        allFileList = null;
        echoRunning();
    }
    
    private static void echoRunning() {
        if (BanBkE2p.threadList.size() == 0) {
            logger.info("=============[" + BanBkE2p.threadList.size() + "]个过程正在运行。");
        } else {
            logger.info(">>>>>>>>>>>>>[" + BanBkE2p.threadList.size() + "]个过程正在运行。");
            Iterator<String> itr = BanBkE2p.threadList.iterator();
            StringBuffer sb = new StringBuffer();
            sb.append("[");
            while (itr.hasNext()) {
                sb.append(itr.next());
                sb.append(",");
            }
            sb.deleteCharAt(sb.length() - 1);
            sb.append("]");
            logger.info(">>>>>>>>>>>>>" + sb.toString());
            sb = null;
        }
    }
    
    public static void traverseFolderBK(String path) {

        File file = new File(path);
        if (file.exists()) {
            File[] files = file.listFiles();
            if (files.length == 0) {
                logger.info("文件夹是空的!");
                return;
            } else {
                for (File file2 : files) {
                    if (file2.isDirectory()) {
                        logger.info("文件夹:" + file2.getAbsolutePath());
                        String jsonPath = file2.getAbsolutePath();
                        if(jsonPath.contains("BK")){
                            execute(jsonPath);
                        }else{
                            traverseFolderBK(file2.getAbsolutePath());
                        }
                        
                    } else {
                        logger.fatal(file2.getAbsolutePath() + " 不是任务目录 。");
                        continue;
                    }
                }
            }
        } else {
            logger.info(path + " 文件夹不存在!");
        }
    }
}
